package library.dao.mysql;

import library.domain.Entity;
import library.exception.DataException;
import java.sql.Connection;
import java.sql.SQLException;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
import library.dao.BookDao;
import library.dao.Dao;
import library.dao.DaoManager;
import library.dao.UserDao;

public class DaoManagerImpl extends DaoManager {

    private static final Map<Class<? extends Dao<? extends Entity>>, Class<? extends Dao<? extends Entity>>> classes = new ConcurrentHashMap<Class<? extends Dao<? extends Entity>>, Class<? extends Dao<? extends Entity>>>();
    private Connection connection;


    static {
        classes.put(UserDao.class, UserDaoImpl.class);
        classes.put(BookDao.class, BookDaoImpl.class);
    }

    public DaoManagerImpl() throws DataException {
        this.connection = ConnectionPool.getInstance().getConnection();
    }

    @Override
    @SuppressWarnings("unchecked")
    public <Type extends Dao<? extends Entity>> Type createDao(Class<Type> key) {
        Class<? extends Dao<? extends Entity>> value = classes.get(key);
        if (value != null) {
            try {
                return (Type) value.getConstructor(Connection.class).newInstance(connection);
            } catch (Exception e) {
            }
        }
        return null;
    }

    @Override
    public void transactionCommit() throws DataException {
        try {
            connection.commit();
        } catch (SQLException e) {
            throw new DataException(e);
        }
    }

    @Override
    public void transactionRollback() throws DataException {
        try {
            connection.rollback();
        } catch (SQLException e) {
            throw new DataException(e);
        }
    }

    @Override
    public void close() {
        ConnectionPool.getInstance().freeConnection(connection);
    }
}